/*
  Copyright (c) 2012 The Chromium Authors. All rights reserved.
  Use of this source code is governed by a BSD-style license that can be
  found in the LICENSE file.
*/

/*
 * Common methods for Subversion change log JS.
 * Requires the GCI service "svn-log" to be set up on the same web server as
 * the one serving this page.
 */

/** @private */
function fix_text_(str, n) {
  if (str.length > n)
    return str.substring(0, n);

  for (var i = str.length; i < n; ++i)
    str = str + ' ';
  return str;
}

/**
 * Gets all log entries.
 * @private
 * @return{Array}
 */
function get_entries_() {
  return gContent.contentDocument.getElementsByTagName("logentry");
}

/**
 * @private
 * @return {Object} An object containing revision information.
 */
function get_info_(entry) {
  var r = new Object;
  r.rev = entry.getAttribute("revision");
  r.author = entry.getElementsByTagName("author")[0].textContent;
  r.msg = entry.getElementsByTagName("msg")[0].textContent;
  r.paths = [];
  var paths = entry.getElementsByTagName("path")
  for (var i = 0; i < paths.length; ++i) {
    r.paths.push({"action" : paths[i].getAttribute("action"),
                  "value"  : paths[i].textContent});
  }
  return r;
}

/** @private */
function render_log_callback_() {
  if ("mode" in params && params.mode == "text") {
    var out = document.createElement("PRE");
    document.body.appendChild(out);

    var entries = get_entries_();
    for (var i = 0; i < entries.length; ++i) {
      var info = get_info_(entries[i]);

      var msg = info.msg;
      msg = msg.replace(/\n/g, ' ' );
      msg = msg.replace(/\t/g, ' ' );
      while (msg.charAt(0) == ' ')
        msg = msg.substring(1);

      var msg_clipped = msg.substring(0, 66);
      if (msg_clipped.length < msg.length)
        msg_clipped = msg_clipped + "...";

      out.appendChild(document.createTextNode(
          fix_text_(info.rev, 6) + " " +
          fix_text_(info.author, 8) + " " +
          msg_clipped + "\n"));
    }
  } else {
    var table = document.createElement("TABLE");
    table.setAttribute("class", "log");
    document.body.appendChild(table);

    var entries = get_entries_();
    for (var i = 0; i < entries.length; ++i) {
      var info = get_info_(entries[i]);

      var tr = document.createElement("TR");
      table.appendChild(tr);

      var td, a;

      // revision:
      td = document.createElement("TD");
      tr.appendChild(td);

      a = document.createElement("A");
      a.setAttribute("href", gViewvcUrl + "?view=rev&revision=" + info.rev);
      a.appendChild(document.createTextNode(info.rev));

      td.appendChild(a);

      // author:
      td = document.createElement("TD");
      tr.appendChild(td);

      a = document.createElement("A");
      a.setAttribute("href", "mailto:" + info.author);
      a.appendChild(document.createTextNode(info.author));

      td.appendChild(a);

      // details:
      td = document.createElement("TD");
      tr.appendChild(td);

      var p = document.createElement("PRE");
      td.appendChild(p);

      var s = info.msg;
      p.appendChild(document.createTextNode(s));

      for (var j = 0; j < info.paths.length; ++j) {
        td.appendChild(document.createTextNode(info.paths[j]["action"] + " - "))
        var a = document.createElement("A");
        a.setAttribute("href", gViewvcUrl + info.paths[j]["value"] + "?r1=" +
            info.rev + "&r2=" + (info.rev - 1) + "&pathrev=" + info.rev);
        a.appendChild(document.createTextNode(info.paths[j]["value"]));
        td.appendChild(a);
        td.appendChild(document.createElement("BR"));
      }
    }
  }
}

/**
 * Renders XML data received from the Subversion server into HTML
 * @param svnRootUrl {string} A Subversion root URL, e.g.
 * 	   http://src.chromium.org/svn/
 * @param svnPath {string} Path from the root to the branch to get the log for.
 * @param svnRange {string} String containing two integers separated by a
 *     colon, where the first is the from-revision and the second is the
 *     to-revision.
 * @param viewvcUrl {string} URL to the ViewVC web application that can be used
 *     to view revisions. This is used for links to revisions.
 */
function render_log(svnRootUrl, svnPath, svnRange, viewvcUrl) {
  if (svnPath == undefined || svnRange == undefined)
    return;
  gViewvcUrl = viewvcUrl;

  var url = "http://" + location.host + "/cgi-bin/svn-log?url=" +
      svnRootUrl + unescape(svnPath) + "&range=" + unescape(svnRange);

  // global 'gContent' variable: a hidden iframe used to fetch svn data.
  gContent = document.createElement("IFRAME");
  gContent.setAttribute("id", "content");
  gContent.setAttribute("onload", "render_log_callback_()");
  gContent.setAttribute("src", url);
  document.body.appendChild(gContent);

  var el;
  if ("mode" in params && params["mode"] == "text") {
    el = document.getElementById("mode_text");
  } else {
    el = document.getElementById("mode_html");
  }
  el.setAttribute("checked", "1");

  el = document.getElementById("url");
  el.setAttribute("value", unescape(svnPath));

  el = document.getElementById("range");
  el.setAttribute("value", unescape(svnRange));
}
